unit u_form;

interface

uses
     u_input,
     Microsoft.DirectX.Direct3D,
     Microsoft.DirectX.Direct3DX,
     Microsoft.DirectX.DirectInput,
     Microsoft.DirectX,
     classes,
     windows,
     system.IO,
     u_load,
     sysutils,
     u_astar,
     u_asus,
     u_resennemi,
     u_surcouf,
     dialogs,
     System.Windows.Forms,
     System.Drawing;

type

c_form = class(form)
  public
    phi, teta, zoom: real;
    texture1, texture2: texture;
    min, max: integer;
    click_x: integer;
    click_y: integer;
    chatx, chaty: integer;
    chat_focus: boolean;
    pclick: boolean;
    presentparam : PresentParameters;
    _3D_device : Microsoft.DirectX.Direct3D.device;
    _height : integer;
    _width : integer;
    suppr: boolean;
    supx: integer;
    supy: integer;
    m_x, m_y : integer;
    fpause: boolean;
    constructor create;
    procedure dispose;
    procedure onresize(e:EventArgs); override;
    procedure onkeydown(e: KeyEventArgs); override;
    procedure onmousemove(e: MouseEventArgs); override;
    procedure onmousedown(e: MouseEventArgs); override;
    procedure onmouseup(e: MouseEventArgs); override;
    procedure show_cursor(caca : boolean);
    procedure change_size(_w, _h : integer);
    procedure set_max(_set: boolean);
end;


implementation

uses u_mesh, u_engine, u_menu, u_ia, u_player;

procedure c_form.set_max(_set : boolean);
  begin
    if _set then
      WindowState := FormWindowState.Maximized
      else
      WindowState := FormWindowState.Normal;
  end;

procedure c_form.change_size(_w: Integer; _h: Integer);
  begin
    Self.ClientSize := System.Drawing.Size.Create(_w, _h);
  end;



procedure c_form.show_cursor(caca: Boolean);
begin
  ShowCursor(true);
end;

procedure c_form.onresize(e: EventArgs);
begin
  FPause := ( ( Self.WindowState = FormWindowState.Minimized ) or ( not Self.Visible ) );
  Self.Text := IntToStr( Self.Size.Width) + ' : ' + IntToStr(Self.Size.Height);
  mymenu.onresize(Self.Width, Self.Height);
  _width := Self.Width;
  _height := Self.Height;
  if not mymenu.show_menu then
    begin
      mygamemenu.onresize(ClientSize.Width, ClientSize.Height);
      mysurcouf.onresize(myform.Width, myform.Height)
    end;
end;


constructor c_form.create;
begin
  inherited create;

  _width := 800;
  _height := 600;
  presentparam := PresentParameters.Create;

  presentparam.Windowed := true;//FullScreenRefreshRateInHz := 60;
  presentparam.SwapEffect := SwapEffect.Discard;
  presentparam.EnableAutoDepthStencil := true;
  presentparam.AutoDepthStencilFormat := DepthFormat.D16;
  presentparam.PresentationInterval := PresentInterval.Immediate;

  self._3D_device := Microsoft.directx.Direct3D.Device.Create(0, Microsoft.directx.Direct3D.DeviceType.hardware, self, CreateFlags.HardwareVertexProcessing, [presentparam]);
  mymenu := c_menu.create(_3D_device);
  self.ClientSize := System.Drawing.Size.Create(_width, _height);
  suppr := false;
  texture1 := textureloader.FromFile(Self._3D_device, 'meshes\image005.jpg');
  texture2 := textureloader.FromFile(Self._3D_device, 'meshes\plop2.bmp');
  chat_focus := false;
  fpause := false;
end;


procedure c_form.onkeydown(e: KeyEventArgs);
var
  myinput: c_input;
  temp: T_Move;
  ennemi: t_tabennemi;
  ennemi_pos: r_ennemi;
  modif: boolean;
begin
  myinput := c_Input.Create;
  myinput := c_Input.KeyandmouseCreate;
  myinput.InitializeKeyboard(self);
  myinput.Keybupdate;

  if mymenu.show_menu then
    begin
      mymenu.on_key(e.KeyValue);
      Exit;
    end;

  if myplayer.mychat.isactive then
    begin
      myplayer.mychat.on_key(e.KeyValue);
      Exit;
    end;

  if myinput.KeyState[Key.I] then
    begin
      mymenu_in_game.menu_ouvert(mymenu_in_game.tou_i, mymenu_in_game.c, mymenu_in_game.p);
    end;

  if myinput.KeyState[Key.c] then
    begin
      mymenu_in_game.menu_ouvert(mymenu_in_game.c, mymenu_in_game.tou_i, mymenu_in_game.p);
    end;


//  if myinput.KeyState[key.b] then
//    begin
//      suppr := true;
//    end;


  if myinput.KeyState[key.p] then
    begin
      mymenu_in_game.menu_ouvert(mymenu_in_game.p, mymenu_in_game.c, mymenu_in_game.tou_i);
    end;

  if myinput.KeyState[key.o] then
    begin
      if myplayer.etage = min then
        exit;
      myplayer.etage := myplayer.etage - 1;
    end;

  if myinput.KeyState[key.Escape] then
    begin
    if not mymenu.show_menu then
      begin
        if mygamemenu._visible then
          mygamemenu.is_visible(false)
        else
          mygamemenu.is_visible(true);
      end;
    end;

  if myinput.KeyState[key.pagedown] then
  begin
    if phi = -math.pi / 2 then
      exit;
    phi := phi - 0.175;
    self.Text:= 'caca';
  end;

  if myinput.KeyState[Key.pageup] then
  begin
    if phi = math.pi / 2 then
      exit;
    phi := phi + 0.175;
  end;

  if myinput.KeyState[Key.a] then
  begin
    teta := teta - 0.175;
  end;

  if myinput.KeyState[Key.d] then
  begin
    teta := teta + 0.175;
  end;



  if myinput.KeyState[key.k] then
    save_map('pipicaca');



  if myinput.KeyState[Key.w] then
  begin
    if zoom <= 2 then
      exit;
    zoom :=zoom- 0.5;
  end;

  if myinput.KeyState[Key.s] then
  begin
    if zoom > 38 then
     exit;
     zoom :=zoom+ 0.5;
  end;

  if myinput.KeyState[Key.x] then
  begin
    if not (myplayer.game_type = 'c') then
      begin
        if (myplayer.selection_pos.exist) and (myplayer.attaque.test)then
          begin
            if myplayer.selection_pos.t = 'Espion' then
              begin
                ennemi := myennemis.recu_tab(1);
                myplayer.kill(mymesh.map1, mymesh.map2,ennemi);
                if not(myplayer.selection_pos.exist)and ((mysenar.mission='Cypher')or(mysenar.mission='Espion'))then
                  mysenar.nbr_ec := mysenar.nbr_ec + 1;
                modif := false;
                while not modif do
                  modif := myennemis.copy_tab(ennemi,1);
              end
            else
              begin
                if myplayer.selection_pos.t = 'Kamikaze' then
                  begin
                    ennemi := myennemis.recu_tab(2);
                    myplayer.kill(mymesh.map1,mymesh.map2,ennemi);
                    if not(myplayer.selection_pos.exist)and (mysenar.mission='Kamikaze')then
                        mysenar.nbr_ec := mysenar.nbr_ec + 1;
                    modif := false;
                    while not modif do
                      modif := myennemis.copy_tab(ennemi,2);
                  end
                else
                  begin
                    if myplayer.selection_pos.t = 'Ennemi dynamique' then
                      begin
                        ennemi := myennemis.recu_tab(3);
                        myplayer.kill(mymesh.map1,mymesh.map2,ennemi);
                        if not(myplayer.selection_pos.exist)and ((mysenar.mission='Warrior')or(mysenar.mission='Ennemi dynamique'))then
                            mysenar.nbr_ec := mysenar.nbr_ec + 1;
                        modif := false;
                        while not modif do
                          modif := myennemis.copy_tab(ennemi,3);
                      end;
                  end;
              end;
          end;
      end
    else
      begin
        if myplayer.selection_pos.exist and myplayer.attaque.test then
          begin
            ennemi_pos := myplayer.myreseauennemis.id_to_coord(myplayer.selection_pos.id);
            myplayer.clientorserveur.send_hitennemi(IntToStr(myplayer.get_x), IntToStr(myplayer.get_y), IntToStr(myplayer.etage), IntToStr(ennemi_pos.x), IntToStr(ennemi_pos.y), IntToStr(ennemi_pos.z), '20');
          end;
      end;
  end;

end;




procedure c_form.dispose;
begin
  _3D_device.Dispose;
end;


procedure c_form.onmousemove (e : MouseEventArgs);
var
  u,v,u1,v1,w: vector3;
  m,mview,mworld: matrix;
  mousex,mousey : integer;
  p :Plane;
begin
//  if  then
//
//  mymenu_in_game.move_menu := true;
  m_x := e.X;
  m_y := e.Y;

  if not mymenu.show_menu then
    begin
      if chat_focus then
        begin
          myplayer.mychat.setpos( e.X - chatx , e.Y - chaty );
          Exit;
        end;

//      myplayer.mychat.show_cursor(e.x, e.y);
      myform._3D_device.Transform.World:=matrix.get_zero;
      myform._3D_device.Transform.World:=
            myform._3D_device.Transform.World.Translation( myplayer.get_x ,0 , myplayer.get_y);

      mousex:=e.x;
      mousey:=e.y;

      m:=(self._3D_device.Transform.Projection);
      mview:=(self._3D_device.Transform.View);
      mworld:=(self._3D_device.Transform.World);


      u:=vector3.Create(mousex,mousey,-100);
      v:=vector3.Create(mousex,mousey,100);

      u1:=vector3.Unproject(u,self._3D_device.Viewport,m,mview,mworld);
      v1:=vector3.Unproject(v,self._3D_device.Viewport,m,mview,mworld);

      p := plane.FromPointNormal(vector3.Create(myplayer.get_x,0,myplayer.get_y),vector3.Create(0,1 ,0));
      w:=plane.IntersectLine(p,u1,v1);


      mymesh.plop.x:=myplayer.get_x+  (w.x) + 0.5;
      mymesh.plop.y:= myplayer.get_y+ (w.z) + 0.5;

    if not (myplayer.game_type = 'c') then
      begin
      if (trunc(mymesh.plop.x) in [0..mymesh.taillex-1])and(trunc(mymesh.plop.y) in [0..mymesh.tailley-1]) then
        begin
           if (mymesh.map1[myplayer.etage][trunc(mymesh.plop.x)][trunc(mymesh.plop.y)]._type='none')
              or (mymesh.map1[myplayer.etage][trunc(mymesh.plop.x)][trunc(mymesh.plop.y)]._type='Mur')then
                begin
                  mymesh.plop.Texture := Texture2;
                 // mymesh.plop.mesh.DrawSubset(0);
                end
           else
              begin
                mymesh.plop.Texture := Texture1;
               // mymesh.plop.mesh.DrawSubset(0);
              end;
        end;
      end
    else
      begin
              if (trunc(mymesh.plop.x) in [0..mymesh.taillex-1])and(trunc(mymesh.plop.y) in [0..mymesh.tailley-1]) then
        begin
           if (myplayer.myreseauennemis.map_client[trunc(mymesh.plop.x)][trunc(mymesh.plop.y)]='none')
              or (myplayer.myreseauennemis.map_client[trunc(mymesh.plop.x)][trunc(mymesh.plop.y)]='Mur')then
                begin
                  mymesh.plop.Texture := Texture2;
                 // mymesh.plop.mesh.DrawSubset(0);
                end
           else
              begin
                mymesh.plop.Texture := Texture1;
               // mymesh.plop.mesh.DrawSubset(0);
              end;
        end;
      end;
            self.Text:=inttostr(e.x)+'     '+inttostr(e.Y);
    end;
end;

procedure c_form.onmousedown (e : MouseEventArgs);
var
temp: T_Move;
begin
  if mymenu.show_menu then
    begin
      mymenu.on_click(e.X, e.Y);
      Exit;
    end;
  if myplayer.mychat.is_clicked(e.X ,e.Y ) then
    begin
      if pclick then
        begin
          chatx := e.X - myplayer.mychat.coordx;
          chaty := e.Y - myplayer.mychat.coordy;
          pclick := false;
        end;
      chat_focus := true;
      Exit;
    end;

  if mygamemenu._visible then
    begin
      mygamemenu.onclick(e.x, e.y, width, height);
      Self.Text := IntToStr(e.x) + ' : ' + IntToStr(e.y);
      Exit;
    end;

  if mysurcouf.visible and (not mysurcouf.goto_surcouf) then
    mysurcouf.onclick(m_x, m_y, Width, height)
  else
    if mysurcouf.visible and  mysurcouf.goto_surcouf then
      mysurcouf.click(m_x, m_y, height, width, myplayer.tab_contenu);


   click_x := trunc(mymesh.plop.x );
   click_y := trunc(mymesh.plop.y );

  if myplayer.game_type = 'c' then
    begin
      if (trunc(mymesh.plop.x ) in [low(myplayer.myreseauennemis.map_client)..high(myplayer.myreseauennemis.map_client)]) and
        (trunc(mymesh.plop.y ) in [low(myplayer.myreseauennemis.map_client[trunc(mymesh.plop.x )])..high(myplayer.myreseauennemis.map_client[trunc(mymesh.plop.x )])]) then
      if (myplayer.myreseauennemis.map_client[(trunc(mymesh.plop.x )),(trunc(mymesh.plop.y ))] = 'Espion') or
          (myplayer.myreseauennemis.map_client[(trunc(mymesh.plop.x )),(trunc(mymesh.plop.y ))] = 'Kamikaze') or
          (myplayer.myreseauennemis.map_client[(trunc(mymesh.plop.x )),(trunc(mymesh.plop.y ))] = 'Ennemi dynamique') then
        begin
          myplayer.selection((trunc(mymesh.plop.x)),(trunc(mymesh.plop.y )), mymesh.map1[0, (trunc(mymesh.plop.x )), trunc(mymesh.plop.y )]._type, mymesh.map2);
        end
      else
        begin
          myplayer.calcul_astar(trunc(mymesh.plop.x ), Trunc(mymesh.plop.y ));
          myplayer.timer.init(100);
        end;
    end
  else
    begin
      if (trunc(mymesh.plop.x ) in [low(mymesh.map1[myplayer.etage])..high(mymesh.map1[myplayer.etage])]) and
        (trunc(mymesh.plop.y ) in [low(mymesh.map1[myplayer.etage, trunc(mymesh.plop.x)])..high(mymesh.map1[myplayer.etage, trunc(mymesh.plop.x)])]) then
      if (mymesh.map1[myplayer.etage,(trunc(mymesh.plop.x )),(trunc(mymesh.plop.y ))]._type = 'Espion') or
          (mymesh.map1[myplayer.etage,(trunc(mymesh.plop.x )),(trunc(mymesh.plop.y ))]._type = 'Kamikaze')or
          (mymesh.map1[myplayer.etage,(trunc(mymesh.plop.x )),(trunc(mymesh.plop.y ))]._type = 'Ennemi dynamique')or
          (mymesh.map1[myplayer.etage,(trunc(mymesh.plop.x )),(trunc(mymesh.plop.y ))]._type = 'Gentil petit asus') then
        begin
          myplayer.selection((trunc(mymesh.plop.x )),(trunc(mymesh.plop.y)), mymesh.map1[myplayer.etage, (trunc(mymesh.plop.x )), trunc(mymesh.plop.y )]._type, mymesh.map2);
          if (mymesh.map1[myplayer.etage,(trunc(mymesh.plop.x )),(trunc(mymesh.plop.y ))]._type = 'Gentil petit asus') then
            begin
              myplayer.mychat.reduite:= false;
              myplayer.mychat.is_active:= true;
              if not(q_or_not) then
                dialoge.tabdial:=nil;
              myplayer.mychat.add_text(affichage(mymesh.map1[myplayer.etage,(trunc(mymesh.plop.x )),(trunc(mymesh.plop.y ))].script,myplayer.mychat.wait));
              posxgpt:=click_x;
              posygpt:=click_y;
            end;
        end
      else
        begin
        if (mymesh.map1[(myplayer.etage),trunc((mymesh.plop.x )),(trunc(mymesh.plop.y ))]._type = 'Escalier montant') then
          begin
            myplayer.prout_etage.monte := true;
            myplayer.prout_etage.x := trunc(mymesh.plop.x );
            myplayer.prout_etage.y := trunc(mymesh.plop.y );
          end
        else
          begin
            if (mymesh.map1[myplayer.etage,(trunc(mymesh.plop.x )),(trunc(mymesh.plop.y ))]._type = 'Escalier descendant') then
              begin
                myplayer.prout_etage.descend := true;
                myplayer.prout_etage.x := trunc(mymesh.plop.x );
                myplayer.prout_etage.y := trunc(mymesh.plop.y );
              end;
          end;
          myplayer.calcul_astar(trunc(mymesh.plop.x ), Trunc(mymesh.plop.y ));
          myplayer.timer.init(100);
        end;
    end;
  myplayer.dep := false;
  suppr := true;
end;


procedure c_form.OnMouseUp(e: MouseEventArgs);
begin
  pclick := true;
  chat_focus := false;
end;

end.
